package com.yitao.cms.service.user.cmsUser;


import com.querydsl.core.types.Order;
import com.querydsl.core.types.OrderSpecifier;
import com.skipper.base.bean.CommonStatus;
import com.skipper.base.bean.DataOutput;
import com.skipper.base.bean.PagedInput;
import com.skipper.base.bean.PagedOutput;
import com.skipper.base.data.querydsl.PredicateBuilder;

import com.skipper.base.service.GenericEntityService;
import com.yitao.cms.constant.UserErrorEnum;
import com.yitao.cms.constant.UserSession;
import com.yitao.cms.dto.operationUser.OperationRoleDto;
import com.yitao.cms.model.operationUser.*;
import com.yitao.cms.utils.BaseUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import javax.persistence.EntityManager;
import javax.servlet.http.HttpServletRequest;
import javax.transaction.Transactional;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;


@Service
public class OperationRoleService extends GenericEntityService<OperationRoleModel, OperationRoleDto, QOperationRoleModel> {


    @Autowired
    private OperationPermissionService permissionService;

    @Autowired
    private OperationRolePermissionService rolePermissionService;
    private BaseUtils base = BaseUtils.getInstance();

    public OperationRoleService(EntityManager entityManager) {
        super(entityManager);
    }

    /**
     * 查询所有的角色(分页)
     *
     * @return
     */
    public PagedOutput rolePageList(Boolean state, PagedInput pagedInput) {
        try {

            PagedOutput<OperationRoleModel> pagedOutput = repository.pagingList(PredicateBuilder.conjunction()
                    .ifNotNullThenAnd(state,() ->Q.state.eq(state))
                    .and(() ->Q.isDelete.eq(false))
                    .get(),pagedInput,new OrderSpecifier<>(Order.DESC,Q.createTime));

            List<OperationRoleDto> roleDtos = pagedOutput.getData().stream().map(it -> {
                OperationRoleDto roleDto = convertEntityToDto(it);
                List<String> permissionIds =rolePermissionService.findPermissionByRoleId(it.getId());
                roleDto.setPermissionIds(permissionIds);
                return roleDto;
            }).collect(Collectors.toList());

            return new PagedOutput(pagedInput,pagedOutput.getTotalElements(),roleDtos);
        } catch (Exception e) {
            logger.error("角色列表 执行错误{}" + e.getMessage());
            return new PagedOutput(pagedInput,0,null);
        }
    }

    /**
     * 查询角色列表
     * @param state
     * @return
     */
    public DataOutput findAllRole(Boolean state) {
        try {
            List<OperationRoleModel> roles= repository.findAll(PredicateBuilder.conjunction()
                    .ifNotNullThenAnd(state,() ->Q.state.eq(state))
                    .and(() ->Q.isDelete.eq(false))
                    .get());
            List<OperationRoleDto> roleDtos = new ArrayList<>();
            for (OperationRoleModel role : roles) {
                OperationRoleDto roleDto = convertEntityToDto(role);
                List<String> permissionIds =rolePermissionService.findPermissionByRoleId(role.getId());
                roleDto.setPermissionIds(permissionIds);
                roleDtos.add(roleDto);
            }
            return new DataOutput<>(roleDtos);
        } catch (Exception e) {
            logger.error("角色列表 执行错误{}" + e.getMessage());
            return new DataOutput(CommonStatus.SERVER_ERROR.getCode(),"查询用户角色是失败!");
        }
    }

    /**
     * 添加修改角色
     * @param
     * @param request
     * @return
     */
    @Transactional
    public DataOutput saveRole(OperationRoleDto roleDto, HttpServletRequest request) {
        try {
            //获取登录信息
            OperationUserCmsModel userSession = UserSession.getUserSession(request);
            if (userSession == null) {
                return new DataOutput(UserErrorEnum.NULL_LOGIN.getCode(), UserErrorEnum.NULL_LOGIN.getDesc());
            }
            OperationRoleModel roleModel = new OperationRoleModel();
            BeanUtils.copyProperties(roleDto,roleModel);
            if (roleModel!=null && !StringUtils.isEmpty(roleModel.getId())){
                OperationRoleModel roleModel1 = queryFactory.select(Q).from(Q).where(Q.id.eq(roleModel.getId())).fetchOne();
                roleModel.setCreateBy(roleModel1.getCreateBy());
                roleModel.setCreateTime(roleModel1.getCreateTime());
                roleModel.setIsDelete(roleModel1.getIsDelete());
                roleModel.setState(roleModel1.getState());
                roleModel.setLastUpdateBy(Long.valueOf(userSession.getId()));
                roleModel.setLastUpdateTime(base.getNow());

            }else {
                OperationRoleModel roleS = repository.findOne(Q.roleName.eq(roleModel.getRoleName()));
                if (roleS!=null){
                    return new DataOutput(CommonStatus.BAD_REQUEST.getCode(), "角色名已存在，请重新输入!");
                }
                roleModel.setState(true);
                roleModel.setIsDelete(false);
                roleModel.setCreateBy(userSession.getId());
                roleModel.setCreateTime(base.getNow());
            }
                OperationRoleModel r = repository.save(roleModel);
                //绑定资源
            if (r!=null &&roleDto.getPermissionIds()!=null && roleDto .getPermissionIds().size()>0){
                rolePermissionService.addRolePermission(r.getId(), roleDto.getPermissionIds());
            }
                return new DataOutput(CommonStatus.SUCCESS);


        } catch (Exception e) {
            logger.error("角色添加 执行异常{}" + e.getMessage());
            return new DataOutput(CommonStatus.SERVER_ERROR.getCode(),"添加角色失败!");
        }
    }

    /**
     * 查询角色详情
     * @param roleId
     * @return
     */
    public DataOutput findRoleById(Long roleId){
        if (roleId!=null){
           OperationRoleModel roleModel= queryFactory.select(Q).from(Q).where(Q.id.eq(roleId)).fetchFirst();
           if (roleModel!=null){
               OperationRoleDto operationRoleDto = convertEntityToDto(roleModel);
               List<String> permissionIds =rolePermissionService.findPermissionByRoleId(roleModel.getId());
               operationRoleDto.setPermissionIds(permissionIds);
               return new DataOutput(operationRoleDto);
           }

        }
        return new DataOutput(CommonStatus.BAD_REQUEST);

    }

    /**
     * 修改角色状态
     * @param roleId
     * @param state
     * @return
     */
    @Transactional
    public DataOutput updateRoleStatus(Long roleId,Boolean state){
        if (roleId!=null){
        int result = repository.updateByWhere(Q.id.eq(roleId),
                  it->it.set(Q.state,state));
         if (result>0){
             return new DataOutput(CommonStatus.SUCCESS);
         }
        }
        return new DataOutput(CommonStatus.BAD_REQUEST);

    }

    /**
     * 查看用户关联的角色
     *
     * @param userId
     * @return
     */
    public OperationRoleModel getRoleByUserId(Long userId) {
        QOperationUserCmsModel qOperationUserModel = QOperationUserCmsModel.operationUserCmsModel;
        QOperationUserRoleModel qOperationUserRoleModel = QOperationUserRoleModel.operationUserRoleModel;
        if (userId!=null){
          OperationRoleModel roleModel =  queryFactory.select(Q).from(qOperationUserModel).leftJoin(qOperationUserRoleModel)
                    .on(qOperationUserModel.id.eq(qOperationUserRoleModel.userId))
                    .leftJoin(Q).on(qOperationUserRoleModel.roleId.eq(Q.id)).where(qOperationUserModel.id.eq(userId)).fetchFirst();
          return roleModel;

        }
        return null;
    }








}
